package gemini.castor.ui.client.page.content.store.catalog.productcatalog;

import gemini.basic.model.Product;
import gemini.basic.model.ProductType;
import gemini.castor.ui.client.constants.I18nConstants;
import gemini.castor.ui.client.mvp.gin.CastorGinjector;
import gemini.castor.ui.client.page.widget.NumberFieldStandard;
import gemini.castor.ui.client.page.widget.productlist.ProductListEvent;
import gemini.castor.ui.client.page.widget.productlist.ProductListHandler;
import gemini.castor.ui.client.page.widget.productlist.ProductListWidget;
import gemini.castor.ui.client.utils.UiConstants;

import java.util.List;

import com.google.gwt.core.client.GWT;
import com.google.gwt.event.dom.client.ChangeEvent;
import com.google.gwt.event.dom.client.HasClickHandlers;
import com.google.gwt.uibinder.client.UiBinder;
import com.google.gwt.uibinder.client.UiField;
import com.google.gwt.uibinder.client.UiHandler;
import com.google.gwt.uibinder.client.UiTemplate;
import com.google.gwt.user.client.ui.Button;
import com.google.gwt.user.client.ui.Composite;
import com.google.gwt.user.client.ui.FlexTable;
import com.google.gwt.user.client.ui.HTML;
import com.google.gwt.user.client.ui.HTMLTable.ColumnFormatter;
import com.google.gwt.user.client.ui.Image;
import com.google.gwt.user.client.ui.ListBox;
import com.google.gwt.user.client.ui.Panel;
import com.google.gwt.user.client.ui.Widget;

public class ProductCatalogView extends Composite implements
		ProductCatalogPresenter.Display {

	@UiTemplate("ProductCatalogView.ui.xml")
	interface MyUiBinder extends UiBinder<Panel, ProductCatalogView> {
	}

	private static final MyUiBinder binder = GWT.create(MyUiBinder.class);

	private ProductType productType;
	private List<ProductType> productTypes;
	private Product product;
	private I18nConstants constants;

	@Override
	public void setProductType(ProductType productType) {
		this.productType = productType;
	}
	
	@Override
	public Product getProduct() {
		return product;
	}

	@Override
	public void setProduct(Product product) {
		this.product = product;
	}
	
	@Override
	public void setProductTypes(List<ProductType> productTypes) {
		this.productTypes = productTypes;
	}
	
	public ProductCatalogView() {
		initWidget(binder.createAndBindUi(this));
		constants = GWT.create(I18nConstants.class);

		pwgProductList.addProductListHandler(new ProductListHandler() {

			@Override
			public void onSelectedProduct(ProductListEvent productListEvent) {
				onChangeSelectedProduct(productListEvent.getSelectedProduct());
			}
		});
	}

	@UiField
	HTML htmProductName;

	@UiField
	HTML htmCompleteDetail;

	@UiField
	Image imgProduct;

	@UiField
	Button btnAddToCart;

	@UiField
	NumberFieldStandard tbxQuantity;

	@UiField
	HTML htmUsage;

	@UiField
	HTML htmOverview;

	@UiField
	HTML htmKeyBenefit;

	@UiField
	HTML htmFastFacts;

	@UiField
	ListBox lbxCategory;
	
	@UiHandler("lbxCategory")
	void onChangeListBox(ChangeEvent event){
		String selectedCode = lbxCategory.getValue(lbxCategory.getSelectedIndex());
		CastorGinjector.INSTANCE.getEventBus().fireEvent(new ProductCatalogEvent(selectedCode));
	}

	@UiField
	FlexTable flxProInfo;

	@UiField
	ProductListWidget pwgProductList;

	@Override
	public void loadData() {
		int selectedIdx = 0;
		lbxCategory.clear();
		for (int i = 0; i < productTypes.size(); i++) {
			lbxCategory.addItem(productTypes.get(i).getName(), productTypes
					.get(i).getCode());
			if(productTypes.get(i).getCode().equals(productType.getCode())){
				selectedIdx = i;
			}
		}

		lbxCategory.setSelectedIndex(selectedIdx);
	
		CastorGinjector.INSTANCE.getEventBus().fireEvent(new ProductCatalogEvent(productType.getCode()));
	}
	
	@Override
	public void onChangedType(Product product) {
		pwgProductList.loadData(productType.getProducts());
		onChangeSelectedProduct(product);
	}

	private void onChangeSelectedProduct(Product product) {
		this.product = product;
		changeProduct();
	}

	public void changeProduct() {
		initProInfo();

		htmUsage.setHTML(product.getProductDetail().getUserGuide());
		htmOverview.setHTML(product.getProductDetail().getOverview());
		htmKeyBenefit.setHTML(product.getProductDetail().getKeyBenefit());
		htmFastFacts.setHTML(product.getProductDetail().getFastFacts());

		imgProduct.setUrl(product.getImageUrl());
		htmProductName.setHTML("<h2>" + product.getName() + "</h2>");
	}

	private void initProInfo() {
		flxProInfo.removeAllRows();

		if (product != null) {
			ColumnFormatter colFmt = flxProInfo.getColumnFormatter();

			colFmt.setWidth(0, "15%");
			colFmt.setWidth(1, "30%");
			colFmt.setWidth(2, "15%");
			colFmt.setWidth(3, "20%");
			colFmt.setWidth(4, "20%");

			// Column title
			flxProInfo.setHTML(0, 0, UiConstants.TAG_BOLB + constants.htmCode()
					+ UiConstants.TAG_BOLB_END);
			flxProInfo.setHTML(0, 1, UiConstants.TAG_BOLB + constants.htmType()
					+ UiConstants.TAG_BOLB_END);
			flxProInfo.setHTML(0, 2,
					UiConstants.TAG_BOLB + constants.htmLabel()
							+ UiConstants.TAG_BOLB_END);
			flxProInfo.setHTML(0, 3,
					UiConstants.TAG_BOLB + constants.htmPoint()
							+ UiConstants.TAG_BOLB_END);
			flxProInfo.setHTML(0, 4,
					UiConstants.TAG_BOLB + constants.htmRetail()
							+ UiConstants.TAG_BOLB_END);
			flxProInfo.getRowFormatter().setStyleName(0, "tableHeader");
			flxProInfo.setStyleName("ftbSummaryDark");

			flxProInfo.setHTML(1, 0, product.getCode());
			flxProInfo.setHTML(1, 1, "Original");
			flxProInfo.setWidget(1, 2, new Image("images/icons/ico_pdf.png"));
			flxProInfo.setHTML(1, 3, String.valueOf(product.getVolumePoint()));
			flxProInfo.setHTML(1, 4, "12");
		}
	}

	@Override
	public Widget asWidget() {
		return this;
	}

	@Override
	public HasClickHandlers getAddToCartClickHandlers() {
		return btnAddToCart;
	}

	@Override
	public short getQuantity() {
		short result = 0;
		if (tbxQuantity.getValue() != null && !tbxQuantity.getValue().isEmpty()) {
			result = Short.parseShort(tbxQuantity.getValue());
		}
		return result;
	}
}
